package com.cqhz.quwan.ui.buy.fragment

import android.content.Context
import android.content.Intent
import android.graphics.Color
import android.graphics.drawable.ColorDrawable
import android.hardware.Sensor
import android.hardware.SensorEvent
import android.hardware.SensorEventListener
import android.hardware.SensorManager
import android.media.SoundPool
import android.os.Build
import android.os.Bundle
import android.os.Vibrator
import android.support.annotation.RequiresApi
import android.view.Gravity
import android.view.View
import android.view.ViewGroup
import android.widget.PopupWindow
import android.widget.TextView
import com.cqhz.quwan.R
import com.cqhz.quwan.common.KeyContract
import com.cqhz.quwan.model.BettingItem
import com.cqhz.quwan.model.Lottery
import com.cqhz.quwan.model.LottoType
import com.cqhz.quwan.ui.base.AbsFragment
import com.cqhz.quwan.ui.buy.BettingMachineActivity
import com.cqhz.quwan.ui.buy.LotteryBettingActivity
import com.cqhz.quwan.ui.buy.adapter.BallAdapter
import com.cqhz.quwan.ui.widget.AutoHeightGridView
import com.cqhz.quwan.util.combine
import com.cqhz.quwan.util.findView
import com.cqhz.quwan.util.random

/**
 * 普通投注
 */
class BettingNormalFragment:AbsFragment() {
    private val redLabel by findView<TextView>(R.id.betting_normal_red_label)
    private val blueLabel by findView<TextView>(R.id.betting_normal_blue_label)
    private val frontUsableCountTv by findView<TextView>(R.id.tv_front_usable_count)
    private val backUsableCountTv by findView<TextView>(R.id.tv_back_usable_count)
    private val redBallGv by findView<AutoHeightGridView>(R.id.red_ball_selector)
    private val blueBallGv by findView<AutoHeightGridView>(R.id.blue_ball_selector)
    private val frontCountLabel by findView<TextView>(R.id.tv_front_count)
    private val backCountLabel by findView<TextView>(R.id.tv_back_count)
    private val resultLabel by findView<TextView>(R.id.label_result)
    private val shakeBtn by findView<TextView>(R.id.tv_shake)
    private val machineSelectBtn by findView<TextView>(R.id.tv_machine_select)
    private val confirmBtn by findView<TextView>(R.id.btn_confirm)
    private val btnClear by findView<TextView>(R.id.tv_ball_clear)
    private val redSelected = ArrayList<Int>()
    private val blueSelected = ArrayList<Int>()
    private lateinit var mSensorManager:SensorManager
    private lateinit var mVibrator:Vibrator
    private lateinit var mSoundPool:SoundPool
    private var mSoundId:Int = -1
    private var mOldShakeTime:Long = -1
    private val mSensorEventListener = object : SensorEventListener{
        override fun onAccuracyChanged(sensor: Sensor?, accuracy: Int) {

        }

        override fun onSensorChanged(event: SensorEvent?) {
            val sensorType = event?.sensor?.type
            val values = event?.values
            if(sensorType == Sensor.TYPE_ACCELEROMETER){
                if((Math.abs(values!![0]) > SENSOR_VALUE
                                || Math.abs(values[1]) > SENSOR_VALUE
                                || Math.abs(values[2]) > SENSOR_VALUE)){
                    val t = System.currentTimeMillis() - mOldShakeTime
                    if(t >= 1500){
                        mVibrator.vibrate(100)
                        mSoundPool.play(mSoundId,1f,1f,1,0,1f)
                        machineSelect()
                        mOldShakeTime = System.currentTimeMillis()
                    }
                }
            }
        }

    }
    private lateinit var redBallAdapter:BallAdapter
    private lateinit var blueBallAdapter:BallAdapter
    private lateinit var redBalls:LottoType.Balls
    private lateinit var blueBalls: LottoType.Balls
    private var allStake = 100L
    private var dropdownMenu1:PopupWindow? = null
    private val dropdownMenu1Size = IntArray(2)
    companion object {
        private const val SENSOR_VALUE = 18
        fun new(redBalls:LottoType.Balls?,
                blueBalls:LottoType.Balls?):BettingNormalFragment {
            val f = BettingNormalFragment()
            val b = Bundle()
            b.putSerializable(KeyContract.RedBalls,redBalls)
            b.putSerializable(KeyContract.BlueBalls,blueBalls)
            f.arguments = b
            return f
        }
    }
    override fun layout(): Int {
        return R.layout.layout_betting_normal
    }

    @RequiresApi(Build.VERSION_CODES.LOLLIPOP)
    override fun initView() {
        redBalls = arguments!![KeyContract.RedBalls] as LottoType.Balls
        blueBalls = arguments!![KeyContract.BlueBalls] as LottoType.Balls
        // 初始化"摇一摇"功能
        mSensorManager = context?.getSystemService(Context.SENSOR_SERVICE) as SensorManager
        mVibrator = context?.getSystemService(Context.VIBRATOR_SERVICE) as Vibrator
        mSoundPool = SoundPool.Builder().setMaxStreams(1).build()
        mSoundId = mSoundPool.load(context,R.raw.shake_sound_male,1)
        // 初始化"机选"菜单
        dropdownMenu1 = createPopupWindow1()
        // 初始化 Label 显示
        val redLabelText = "${redBalls.label}：已选"
        val blueLabelText = "${blueBalls.label}：已选"
        val frontText = "个（可选${redBalls.selectMin}-${redBalls.selectMax}个红球）"
        val backText = "个（可选${blueBalls.selectMin}-${blueBalls.selectMax}个蓝球）"

        redLabel?.text = redLabelText
        blueLabel?.text = blueLabelText
        frontUsableCountTv?.text = frontText
        backUsableCountTv?.text = backText
        confirmBtn?.setOnClickListener {
            if(redSelected.size >= redBalls.selectMin?:0
                    && blueSelected.size >= blueBalls.selectMin?:0){
                val intent = Intent(context,LotteryBettingActivity::class.java)
                intentWrapper(intent)
                val bi = BettingItem(redSelected,blueSelected,Lottery.TYPE_LOTTO_NORMAL,allStake)
                intent.putExtra(KeyContract.BettingItem,bi)
                startActivity(intent)
            }else{
                showToast("至少选择一注")
            }
        }
        // 初始化数据适配器
        redBallAdapter = BallAdapter(context(),R.layout.item_red_ball)
        blueBallAdapter = BallAdapter(context(),R.layout.item_blue_ball)
        redBallAdapter.listener = {
            redSelected.clear()
            redSelected.addAll(it)
            resetViews()
        }
        blueBallAdapter.listener = {
            blueSelected.clear()
            blueSelected.addAll(it)
            resetViews()
        }

        redBallGv?.adapter = redBallAdapter
        blueBallGv?.adapter = blueBallAdapter
        redBallAdapter.setData(redBalls.range!!)
        blueBallAdapter.setData(blueBalls.range!!)
        if (redBalls.selected != null){
            redBallAdapter.setChecks(redBalls.selected!!)
        }
        if(blueBalls.selected != null){
            blueBallAdapter.setChecks(blueBalls.selected!!)
        }
        shakeBtn?.setOnClickListener {
            machineSelect()
        }
        machineSelectBtn?.setOnClickListener {
            val location = IntArray(2)
            it.getLocationOnScreen(location)

            dropdownMenu1?.showAtLocation(it,
                    Gravity.NO_GRAVITY,
                    location[0]-dropdownMenu1Size[0],
                    location[1]-dropdownMenu1Size[1]-10)
        }
        btnClear?.setOnClickListener {
            redBallAdapter.clearChecks()
            blueBallAdapter.clearChecks()
        }
        resetViews()
    }
    private fun intentWrapper(intent:Intent):Intent{
        val lotteryId = (activity as BettingMachineActivity).currentLotteryId
        val periodNum = (activity as BettingMachineActivity).currentPeriodNum
        val isReset = (activity as BettingMachineActivity).isReset
        val resetIndex = (activity as BettingMachineActivity).resetIndex
        val lotteryName = (activity as BettingMachineActivity).currentLotteryName
        intent.putExtra(KeyContract.LotteryId,lotteryId)
        intent.putExtra(KeyContract.PeriodNum,periodNum)
        intent.putExtra(KeyContract.IsReset,isReset)
        intent.putExtra(KeyContract.LotteryName,lotteryName)
        intent.putExtra(KeyContract.ResetIndex,resetIndex)
        return intent
    }

    private fun genRandomBalls(balls:LottoType.Balls):List<Int>?{
        return balls.range?.random(balls.selectMin)?.sorted()
    }
    private fun machineSelect(){
        redBallAdapter.setChecks(genRandomBalls(redBalls))
        blueBallAdapter.setChecks(genRandomBalls(blueBalls))
        resetViews()
    }
    private fun machineSelectWrapped(count:Int):ArrayList<BettingItem>{
        val list = ArrayList<BettingItem>()
        for (i in 0..count){
            val mRedBalls = genRandomBalls(redBalls)
            val mBlueBalls = genRandomBalls(blueBalls)
            if(mRedBalls != null && mBlueBalls != null){
                val mAllStake = mRedBalls.size.combine(redBalls.selectMin?:0)*
                        mBlueBalls.size.combine(blueBalls.selectMin?:0)
                list.add(BettingItem(mRedBalls,blueSelected,Lottery.TYPE_LOTTO_NORMAL,mAllStake))
            }
        }
        return list
    }
    override fun onPause() {
        super.onPause()
        mSensorManager.unregisterListener(mSensorEventListener)
    }

    override fun onStart() {
        super.onStart()
        val mSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER)
        mSensorManager.registerListener(mSensorEventListener,mSensor,SensorManager.SENSOR_DELAY_UI)
    }
    override fun onHiddenChanged(hidden: Boolean) {
        super.onHiddenChanged(hidden)
        if(hidden){
            mSensorManager.unregisterListener(mSensorEventListener)
        }else{
            val mSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER)
            mSensorManager.registerListener(mSensorEventListener,mSensor,SensorManager.SENSOR_DELAY_UI)
        }
    }
    private fun resetViews(){
        frontCountLabel?.text  = "${redSelected.size}"
        backCountLabel?.text  = "${blueSelected.size}"
        allStake = redSelected.size.combine(redBalls.selectMin?:0)*
                blueSelected.size.combine(blueBalls.selectMin?:0)
        val text = "已选 $allStake 注\n一共 ${allStake*2} 趣豆"
        resultLabel?.text = text
    }
    private fun createPopupWindow1(): PopupWindow {
        val view = layoutInflater.inflate(R.layout.layout_drapdown, null,false)
        val one = view.findViewById<TextView>(R.id.dropdown_one)
        val five = view.findViewById<TextView>(R.id.dropdown_five)
        val ten = view.findViewById<TextView>(R.id.dropdown_ten)
        one.setOnClickListener {
            dropdownMenu1?.dismiss()
            val intent = Intent(context,LotteryBettingActivity::class.java)
            intentWrapper(intent)
            intent.putExtra(KeyContract.Gen,1)
            startActivity(intent)
        }
        five.setOnClickListener {
            dropdownMenu1?.dismiss()
            val intent = Intent(context,LotteryBettingActivity::class.java)
            intentWrapper(intent)
            intent.putExtra(KeyContract.Gen,5)
            startActivity(intent)
        }
        ten.setOnClickListener {
            dropdownMenu1?.dismiss()
            val intent = Intent(context,LotteryBettingActivity::class.java)
            intentWrapper(intent)
            intent.putExtra(KeyContract.Gen,10)
            startActivity(intent)
        }
        view.measure(View.MeasureSpec.UNSPECIFIED, View.MeasureSpec.UNSPECIFIED)
        dropdownMenu1Size[0] =view.measuredWidth
        dropdownMenu1Size[1] =view.measuredHeight
        val window = PopupWindow(view,
                ViewGroup.LayoutParams.WRAP_CONTENT,
                ViewGroup.LayoutParams.WRAP_CONTENT,
                true)
        window.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
        window.isOutsideTouchable = true
        window.isTouchable = true
        return window
    }
}